package org.androidpn.server.xmpp.push;

import org.androidpn.server.entity.Role;
import org.androidpn.server.entity.Room;
import org.androidpn.server.entity.User;
import org.androidpn.server.service.RoleService;
import org.androidpn.server.service.RoomService;
import org.androidpn.server.service.ServiceLocator;
import org.androidpn.server.service.UserService;
import org.androidpn.server.xmpp.packet.RoomPacket;
import org.androidpn.server.xmpp.session.ClientSession;
import org.androidpn.server.xmpp.session.SessionManager;
import org.apache.commons.logging.Log;
import org.apache.commons.logging.LogFactory;
import org.dom4j.Document;
import org.dom4j.DocumentException;
import org.dom4j.DocumentHelper;
import org.dom4j.Element;
import org.jivesoftware.smack.util.StringUtils;
import org.xmpp.packet.IQ;

/**
 * 推送游戏房间信息线程
 * 
 * @author 蔡琪
 * 
 */
public class PushRoomToClientThread implements Runnable {

	protected final Log log = LogFactory.getLog(getClass());

	private Long roomID;
	private RoomService roomService;
	private UserService userService;
	private RoleService roleService;
	private SessionManager sessionManager;

	public PushRoomToClientThread(Long roomID, SessionManager sessionManager) {
		roomService = (RoomService) ServiceLocator
				.getService(ServiceLocator.ROOM_SERVICE);
		userService = (UserService) ServiceLocator
				.getService(ServiceLocator.USER_SERVICE);
		roleService = (RoleService) ServiceLocator
				.getService(ServiceLocator.ROLE_SERVICE);
		this.roomID = roomID;
		this.sessionManager = sessionManager;
	}

	public void run() {
		Room room = roomService.find(roomID);
		if (room != null) {
			if (room.getRoles().size() <= 0) {
				// 删除房间信息
				roomService.delete(room.getId());
			} else {
				for (Role role : room.getRoles()) {
					User user = role.getUser();
					ClientSession session = sessionManager.getSession(user
							.getUsername().toLowerCase());
					if (session == null) {
						role = roleService.find(role.getId());
						user = userService.find(user.getId());
						user.setOnline(false);
						role.setIsOnline(false);
						role.setIsReady(false);
						role.setRoom(null);
						room.getRoles().remove(role);
						roomService.update(room);
						roleService.update(role);
						userService.update(user);
					} else {
						if (room.getHost() == null) {
							room.setHost(role);
							roomService.update(room);
						}
						RoomPacket roomPacket = new RoomPacket();
						roomPacket.setRoom(room);
						IQ iq = new IQ();
						iq.setID("PushRoomToClientThread");
						iq.setTo(session.getAddress());
						if (roomPacket.getChildElementXML() != null) {
							Document doc;
							try {
								doc = DocumentHelper.parseText(roomPacket
										.getChildElementXML());
								Element element = doc.getRootElement();
								iq.setChildElement(element.createCopy());
								iq.setType(IQ.Type.result);
								log.debug("send "
										+ StringUtils.unescapeNode(iq.toXML()));
								session.process(iq);
							} catch (DocumentException e) {
								e.printStackTrace();
							}
						}
					}
				}
			}
		}
	}
}